<?php
include_once 'recipients_protoweb.php';

/**
 * @package Protoweb
 * @subpackage controller
 */
class Recipients extends Recipients_protoweb {

  public function __construct() {
    parent::__construct();
  } // end of method __construct()


  public function unsubscribe($unsubscribe_key) {
    // the key has the format:
    // recipient_id-sha1(recipient_id+campaign_id)-campaign_id
    $keys = explode('-', $unsubscribe_key);
    $data['recipient'] = new Recipient($keys[0]);

    if (sha1($data['recipient']->id + $keys[2]) === $keys[1]) {

      // get recipients' subscriptions. Only catalogs of the same client as the campaign passed
      $data['recipient_catalogs'] = new Catalog();
      $data['recipient_catalogs']->where_related_subscriber('recipient_id',$data['recipient']->id)->where_related_client('id',$data['recipient']->client->id)->get();

      $this->smarty_parser->view('recipient_unsubscribe.html', $data);
    }
  } // unsubsscibe

  public function unsubscribe_do() {
    $recipient           = new Recipient($this->input->post('recipient_id'));
    $subscriptions       = new Subscriber();
    $subscriptions_count = new Subscriber();

    // build query to recipient's catalogs
    $subscriptions->where_related_recipient('id',$recipient->id)->where_related_catalog('client_id',$recipient->client->id);
    $subscriptions_count->where_related_recipient('id',$recipient->id)->where_related_catalog('client_id',$recipient->client->id);

    if ($this->input->post('catalogs')) {
      foreach ($this->input->post('catalogs') as $catalog) {
        $subscriptions->where_related_catalog('id !=', intval($catalog));
        $subscriptions_count->where_related_catalog('id !=', intval($catalog));
      }
    }

    if ($subscriptions_count->count() == 0) {
      $data['success'] = 'Tu información se actualizó correctamente';
    }
    else {
      $subscriptions->get();
      if ($subscriptions->delete()) {
        $data['success'] = 'Tu información se actualizó correctamente';
      }
      else {
        $data['error'] = 'Ocurrió un error, por favor intentalo otra vez';
      }
    }

    if ($recipient->subscriber->count == 0) {
      $recipient->offdate = date('Y-m-d H:i:s');
      $recipient->offreason = 'Unsubscribe_link';
      $recipient->save();
    }

    $this->smarty_parser->view('recipient_unsubscribe_do.html', $data);
  } // unsubsscibe


  public function create() {
    // Get global instance's objects
    $data['user']   = $this->security();
    $data['client'] = $this->get_client();

    $data["recipient"] = new Recipient();

    if ($this->input->server('REQUEST_METHOD') === 'POST') {
      $data = $this->create_save($data["recipient"]->id);
    }

    $data['offreasons'] = array(
      ''                 => 'Activo', 
      'unsubscribe_request' => 'El contacto solicitó la baja',
      'unsubscribe_desired' => 'No enviar más a este contacto',
      'Bounces'          => 'Demasiados rebotes',
      'SES tries'        => 'Intentos fallidos',
      'dns-hard'         => 'Error de hardware de DNS',
      'dns-soft'         => 'Error de software de DNS',
      'complaint'        => 'Baja de suscripción por spam',
      'Unsubscribe_link' => 'Baja de suscripción por link'
    );
    
    $this->smarty_parser->view('recipient_edit.html', $data);
  } // end of method edit($id=0)


  protected function create_save($id) {
    // Get global instance's objects
    $data['user']   = $this->security();
    $data['client'] = $this->get_client();
    $data["error"] = "";
    $data["recipient"] = new Recipient($id);

    // Assign value to field. If value is empty, we will assign NULL
    $data["recipient"]->email     = $this->input->post("email");
    $data["recipient"]->firstname = $this->input->post("firstname");
    $data["recipient"]->lastname  = $this->input->post("lastname");
    $data["recipient"]->nickname  = $this->input->post("nickname");
    $data["recipient"]->offreason = NULL;
    $data["recipient"]->offdate = 0;
    $data["recipient"]->verified = TRUE;
    $data["recipient"]->client_id = $data['client']->id;

    //saving attributes
    if( ! $data["recipient"]->save($data['client'])) {
      $data["error"] .= $data["recipient"]->error->string;
      return $data;
    }

    // agrega el recipient a todos los catalogos del cliente;
    foreach ($data['client']->catalogs as $catalog) {
      $subscriber = new Subscriber();
      $subscriber->subscribed = date('Y-m-d H:i:s');
      $subscriber->save(array($data["recipient"], $catalog));
    }
                            
    redirect(base_url()."recipients/edit/".$data["recipient"]->id . "/");
  } // end of method edit_save($id)

  public function edit($id=0) {
    // Get global instance's objects
    $data['user']   = $this->security();
    $data['client'] = $this->get_client();

    if ($id == 0) {
      redirect(base_url()."recipients/create/");
    }

    $data["recipient"] = new Recipient($id);

    if ($this->input->server('REQUEST_METHOD') === 'POST') {
      $data = $this->edit_save($data["recipient"]->id);
    }

    $data['offreasons'] = array(
      ''                 => 'Activo', 
      'unsubscribe_request' => 'El contacto solicitó la baja',
      'unsubscribe_desired' => 'No enviar más a este contacto',
      'Bounces'          => 'Demasiados rebotes',
      'SES tries'        => 'Intentos fallidos',
      'dns-hard'         => 'Error de hardware de DNS',
      'dns-soft'         => 'Error de software de DNS',
      'complaint'        => 'Baja de suscripción por spam',
      'Unsubscribe_link' => 'Baja de suscripción por link'
    );
    
    $this->smarty_parser->view('recipient_edit.html', $data);
  } // end of method edit($id=0)

  protected function edit_save($id) {
    $data["error"] = "";
    $data["recipient"] = new Recipient($id);

    // Assign value to field. If value is empty, we will assign NULL
    $data["recipient"]->email     = $this->input->post("email");
    $data["recipient"]->firstname = $this->input->post("firstname");
    $data["recipient"]->lastname  = $this->input->post("lastname");
    $data["recipient"]->nickname  = $this->input->post("nickname");
    $data["recipient"]->offreason = $this->input->post("offreason");

    if ($data['recipient']->offreason != '') {
      $data['recipient']->offdate = date('Y-m-d H:i:s');
    }
    else {
      $data['recipient']->offdate = 0;
    }

    // // Assign value to field. If value is empty, we will assign NULL
    // $data["recipient"]->verified = $this->input->post("verified");
    // if ($data["recipient"]->verified == "") $data["recipient"]->verified = NULL;

    //saving attributes
    if( ! $data["recipient"]->save()) {
      $data["error"] .= $data["recipient"]->error->string;
      return $data;
    }
                            
    redirect(base_url()."recipients/edit/".$data["recipient"]->id . "/");
  } // end of method edit_save($id)

  public function join($slug="") {
    $data["recipient"] = new Recipient();

    // To one relationships
    $data["client"] = new Client();
    $data["client"]->where("slug", $slug)->get();

    if ($this->input->server('REQUEST_METHOD') === 'POST')
      $data = $this->join_save($data["client"]->id);
    
    if($data["client"]->id) 
      $this->smarty_parser->view('recipient_join.html', $data);
  } // end of method join($slug="")


  protected function join_save($client_id) {
    $client            = new Client($client_id);
    $data["recipient"] = new Recipient();

    // Assign attributes
    $data["recipient"]->email     = $this->input->post("email");
    $data["recipient"]->firstname = $this->input->post("firstname");
    $data["recipient"]->lastname  = $this->input->post("lastname");      
    $data["recipient"]->created   = date('Y-m-d H:i:s');
    $data["recipient"]->verified  = 1;      
    $data["recipient"]->sends     = 0;
    $data["recipient"]->bounceds  = 0;      
    
    // saving attributes and relationships
    if ( ! $data["recipient"]->save(array($client)))
      $data["error"] .= $data["recipient"]->error->string;
                            
    redirect(base_url()."recipients/edit/".$data["recipient"]->id);
  } // end of method join_save($cleint_id)


  public function import() {
    // Users Security and selected client
    $user   = $this->security();
    $client = $this->get_client();

    $data = array(
      "user" => $user, 
      "client" => $client
    );
    $this->smarty_parser->view('recipient_import.html', $data);
  }

  public function import_status() {
    // Get global instance's objects
    $user   = $this->security();
    $client = $this->get_client();

    define('LOG_PROGRESS', $this->config->item('clients_path') . $client->slug . '/import_progress.log');
    $import_progress = file_get_contents(LOG_PROGRESS);

    echo $import_progress; // have json format
  }


  public function import_ajaxupload() {
    // Get global instance's objects
    $user   = $this->security();
    $client = $this->get_client();

    define('OUTPUT_PATH',  $this->config->item('clients_path') . $client->slug . '/');
    define('OUTPUT_FILE',  'import_contacts');

    $config['upload_path'] = OUTPUT_PATH;
    $config['allowed_types'] = 'xls';
    $config['max_size'] = '50000'; // 50 Mbytes
    $config['file_name'] = OUTPUT_FILE;
    $config['overwrite'] = TRUE;

    $this->load->library('upload', $config);

    if ( ! $this->upload->do_upload() ) {
      $data->success = FALSE;
    }
    else {
      $data->success = TRUE;
    }

    echo json_encode($data);
  }


  public function import_do() {
    // Get global instance's objects
    $user   = $this->security();
    $client = $this->get_client();

    define('LOG_INVALIDS',   $this->config->item('clients_path') . $client->slug . '/import_invalid.log');
    define('LOG_PROGRESS',   $this->config->item('clients_path') . $client->slug . '/import_progress.log');
    define('CONTACTS_FILE',  $this->config->item('clients_path') . $client->slug . '/import_contacts.xls');
    define('LOG_PHP_ERRORS', $this->config->item('clients_path') . $client->slug . '/php_errors.log');

    // limpiamos la lista anterior
    if (file_exists(LOG_INVALIDS))
      unlink(LOG_INVALIDS);

    error_reporting(E_ALL | E_STRICT); //For PHP 6 E_STRICT become part of E_ALL
    ini_set('display_errors', 'Off');
    ini_set('log_errors', 'On');
    ini_set('error_log', LOG_PHP_ERRORS);

    ini_set("memory_limit","-1"); // unlimited
    set_time_limit(0); // unlimited

    $this->load->library("Spreadsheet_Excel_Reader");

    $excel      = new Spreadsheet_Excel_Reader(CONTACTS_FILE);
    $sheet      = 0;
    $rowfrom    = 2; // evitamos la primera linea que tiene titulos
    $rowto      = $excel->rowcount($sheet);


    // Si los emails a importar superan el 20% de los contactos del cliente,
    // forzaremos el chequeo semántico por DNS
    if ($rowto > $client->count_recipients() * 0.2)
      $chek_real_email = TRUE;
    else
      $chek_real_email = FALSE;


    $import_values = array(
      'total'     => $rowto-1, 
      'imported'  => 0, 
      'invalid'   => 0, 
      'processed' => 0, 
      'percent'   => 0
    );

    $contacts = new Recipient();
    $contacts->select('email');
    $contacts->where("client_id", $client->id);
    $contacts->get();

    $recipients = array();
    foreach ($contacts as $recipient) {
      array_push($recipients, $recipient->email);
    }
    $contacts->clear(); // free $contacts

    for($row = $rowfrom; $row <= $rowto; $row++) {
      $contact = new Recipient();
      $contact->email     = trim($excel->val($row,1,$sheet));
      $contact->firstname = trim($excel->val($row,2,$sheet));
      $contact->lastname  = trim($excel->val($row,3,$sheet));
      $contact->created   = date('Y-m-d H:i:s');
      $contact->verified  = 1;
      $contact->sends     = 0;
      $contact->bounces   = 0;
      $contact->offdate   = 0;

/*
      // Si chequeamos real email y no es válido, 
      // cortamos y continuamos con el próximo contacto
      if ($chek_real_email) {
        if (!valid_real_email($contact->email)) {
          break;
        }          
      }
*/

      // generamos un array con las claves, quitamos los espacios y eliminamos los vacíos
      $contact->claves    = array_filter(array_map("trim", explode(",",trim($excel->val($row,4,$sheet)))));

      if (! in_array ($contact->email, $recipients )) {

        if ($contact->save(array($client))) {
          array_push($recipients, $contact->email); // esto es para evitar que se cargue de nuevo el mismo email
          
          $import_values["imported"]++;

          foreach ((array)$contact->claves as $clave) {
            $attribute = $client->attribute->where("name",$clave)->get();
            
            // Si el atributo no existe en la base de datos, lo agregamos
            if (! $attribute->id) {
              $attribute = new Attribute();
              $attribute->name = $clave;
              $attribute->type = "boolean";
              $attribute->save($client);
            }

            // Agregamos el valor del atributo y lo relacionamos al recipient (contacto)
            $attrvalue = new Attrvalue();
            $attrvalue->value = TRUE;
            $attrvalue->save(array($attribute, $contact));
          }


          // agrega el recipient a todos los catalogos del cliente;
          foreach ($client->catalogs as $catalog) {
            $subscribe = new Subscriber();
            $subscribe->subscribed = date('Y-m-d H:i:s');
            $subscribe->save(array($contact, $catalog));
          }

        } // contact->save
        else {
          // agregamos el contact a la lista de no procesados
          $rowlog = "'{$contact->email}','{$contact->firstname}','{$contact->lastname}','{$contact->claves}'\r\n";
          error_log($rowlog,3,LOG_INVALIDS);

          $import_values["invalid"]++;
        }
      } // if ! in_array

      $import_values["processed"]++;
      $import_values["percent"] = round($import_values["processed"] / $import_values["total"] * 100);
      file_put_contents(LOG_PROGRESS, json_encode($import_values));

    } // for excel rows

    if (file_exists(LOG_PROGRESS))
      unlink(LOG_PROGRESS);

    if (file_exists(CONTACTS_FILE))
      unlink(CONTACTS_FILE);

    echo json_encode($import_values);
  } // end import_do


  public function search_post() {
    redirect(base_url()."recipients/search/".$this->input->post('keyword')."/");
  }


  public function search($keyword="") {
    // Get global instance's objects
    $data['user']   = $this->security();
    $data['client'] = $this->get_client();
    $data["keyword"] = $keyword;

    if ($keyword != "") {
      $data["recipients"] = new Recipient();
      $data["recipients"]->select('id, email, firstname, lastname');
      $data["recipients"]->group_start();
      $data["recipients"]->ilike('email',$keyword);
      $data["recipients"]->or_ilike('firstname',$keyword);
      $data["recipients"]->or_ilike('lastname',$keyword);
      $data["recipients"]->group_end();
      $data["recipients"]->where_related_client('id',$data['client']->id);
      $data["recipients"]->order_by('email');
      $data["recipients"]->get();
    }

//die($data["recipients"]->check_last_query());

    $this->smarty_parser->view('recipient_search.html', $data);
  }


} // class Recipients

/* End of file recipients.php */
/* Location: ./system/application/controllers/recipients.php */